#include <os_common_api.h>
#include <string.h>
#include <stdlib.h>
#include <stdio.h>
#include <bt_manager.h>
//#include "btmusic.h"
#include "uart_control.h"
#include "app_defines.h"
#include "input_manager.h"
#include "app_manager.h"
#include "app_switch.h"
#include "volume_manager.h"
#include "audio_system.h"
#include "sys_manager.h"
#include "power_manager.h"
#include "sys_event.h"





static struct uart_buf_info uart_buf[UART_BUF_QUEUED];
struct uart_data_format send_cache;			/* 串口TX临时缓存区 */

u8_t rx_data[2][UART_MTU];
u8_t rx_index[2]={0};

u8_t alarm_ringing_enable;
u8_t mcu_is_ready=0;
struct uart_msg_info remote_dev_info;

static K_FIFO_DEFINE(cmds_queue_uart1);
static K_FIFO_DEFINE(avail_queue_uart1);
static os_delayed_work uart1_control_run_delaywork;
extern void system_stop_sync(void);
extern void system_sync_to_remote_start(u8_t sync_mode,u8_t cmd);

extern u8_t system_get_mic_status(void);
extern void audio_set_cascade_in(void);
extern void audio_input_set_hung_led(u8_t call_flag);
extern void audio_aux_sync_remote_volume(u8_t sync_vol);
extern void usound_set_tts_tone(u8_t mode);
extern u8_t audio_aux_get_status(void);
extern u8_t get_sync_flag(void);
extern u8_t sys_check_ap_ready(void);



/**
 * uart1 tx send
 *
 * @param
 *  p_data
 */
void uart1_send_to_apt(     u8_t *p_data,u8_t writen_len)
{
    //SYS_LOG_INF(" reply3 %d\n", writen_len);
    if(writen_len > UART_MTU){
        SYS_LOG_ERR("uart1: TX data_len err.");
        return;
    }
    if(writen_len ==0){
        SYS_LOG_ERR("uart1: TX cmd_len err.");
        return;
    }
	printk("TX:\n");
    print_buffer(p_data, 1, writen_len, 16, 0);
    uart_pipe_send((u8_t *)p_data, writen_len);
}

void get_cur_status(void)
{
	if(strcmp(app_manager_get_current_app(), APP_ID_BTMUSIC)==0)
	{
		u16_t bt_state;
		bt_state=bt_manager_get_status()&BT_STATUS_PLAYING;
	}
	else if(strcmp(app_manager_get_current_app(), APP_ID_LINEIN)==0)
	{
		
	}
}
//len+cmd+param
u8_t get_checksum(u8_t *data,u8_t length)
{
	u16_t checksum=0,i=0;
	for(i=0;i<length;i++)
	{
		checksum+=data[i];
	}
	checksum=0xFF-(checksum&0xFF);
	printf("cur checksum:0x%x\n",checksum);
	return checksum;
}
#define HEAD_OFFSET 0
#define LEN_OFFSET 1
#define CMD_OFFSET 2
#define PARAM_OFFSET 3
#define CHECKSUM_OFFSET 4
#define END_OFFSET 5
void sys_get_remote_info(struct uart_msg_info* remote_info)
{
	memcpy(remote_info,&remote_dev_info,sizeof(struct uart_msg_info));
}
void report_msg_to_main(u8_t msg_cmd,u8_t msg_data)
{
	struct app_msg  msg = {0};
	msg.type = msg_cmd;
	msg.content[0]=msg_data;
	send_async_msg("main", &msg);
}
void report_msg_to_cur_ap(u8_t msg_type,u8_t msg_cmd,u8_t msg_data)
{
	struct app_msg  msg = {0};
	msg.type = msg_type;
	msg.cmd =msg_cmd;
	msg.content[0]=msg_data;
	send_async_msg(app_manager_get_current_app(), &msg);
	#if 0
	if (strcmp(app_manager_get_current_app(), APP_ID_USOUND) == 0)
	{
		send_async_msg(APP_ID_USOUND, &msg);
	}
	else if (strcmp(app_manager_get_current_app(), APP_ID_BTMUSIC) == 0)
	{
		send_async_msg(APP_ID_BTMUSIC, &msg);		
	}
	else if (strcmp(app_manager_get_current_app(), APP_ID_BTCALL) == 0)
	{
		send_async_msg(APP_ID_BTCALL, &msg);
	}
	else if (strcmp(app_manager_get_current_app(), APP_ID_LINEIN) == 0)
	{
		send_async_msg(APP_ID_LINEIN, &msg);
	}
	else
	{
		SYS_LOG_INF("cur app err:%s\n",(char*)app_manager_get_current_app());
	}
	#endif
}
void deal_remote_bt_status(void)
{	
	if (strcmp(app_manager_get_current_app(), APP_ID_BTMUSIC) == 0)
	{
		if(remote_dev_info.bt_status>=1)
		{
			report_msg_to_main(MSG_SWITCH_AP_SLAVER,0);			
		}
	}
	else if (strcmp(app_manager_get_current_app(), APP_ID_USOUND) == 0)
	{
		if(remote_dev_info.bt_status>=1)
		{
			report_msg_to_main(MSG_SWITCH_AP_SLAVER,0);
		}
	}
	else if (strcmp(app_manager_get_current_app(), APP_ID_LINEIN) == 0)
	{
		SYS_LOG_INF("remote bt status:%d\n",remote_dev_info.bt_status);
		if(remote_dev_info.bt_status==0)
		{
			report_msg_to_main(MSG_SWITCH_AP_MASTER,0);	
		}
		else if(remote_dev_info.bt_status==2)
		{
			audio_input_set_hung_led(1);
		}
		else if(remote_dev_info.bt_status==3)
		{
			audio_input_set_hung_led(2);
		}
		else
		{
			audio_input_set_hung_led(0);
		}
	}
}
void deal_remote_usb_status(void)
{
	if(remote_dev_info.usb_status!=2)
	{
		return;
	}
	if (strcmp(app_manager_get_current_app(), APP_ID_BTMUSIC) == 0)
	{
		if((bt_manager_get_status()&BT_STATUS_CONNECTED)!=BT_STATUS_CONNECTED)
		{
			report_msg_to_main(MSG_SWITCH_AP_SLAVER,0);	
		}		
	}
	else if (strcmp(app_manager_get_current_app(), APP_ID_USOUND) == 0)
	{
		report_msg_to_main(MSG_SWITCH_AP_SLAVER,0);
	}
	else if (strcmp(app_manager_get_current_app(), APP_ID_LINEIN) == 0)
	{
		audio_input_set_hung_led(0);
	}
}
void deal_remote_poweroff(void)
{
	if (strcmp(app_manager_get_current_app(), APP_ID_LINEIN) == 0)
	{
		report_msg_to_main(MSG_SWITCH_AP_MASTER,0);	
	}	
}
void deal_cascade_status_to_aux(void)
{
	if (strcmp(app_manager_get_current_app(), APP_ID_LINEIN) == 0)
	{
		audio_set_cascade_in();	
	}	
}

void deal_ack_info_msg(struct uart_msg_info* msg_info)
{
	if(remote_dev_info.ap_mode>=4)
	{
		return;//remote ap not ready
	}
	if (strcmp(app_manager_get_current_app(), APP_ID_BTMUSIC) == 0)
	{
		if(remote_dev_info.bt_status>=1&&((bt_manager_get_status()&BT_STATUS_CONNECTED)!=BT_STATUS_CONNECTED))
		{
			report_msg_to_main(MSG_SWITCH_AP_SLAVER,0);			
		}
		else if(remote_dev_info.usb_status==2)
		{
			if((bt_manager_get_status()&BT_STATUS_CONNECTED)!=BT_STATUS_CONNECTED)
			{
				report_msg_to_main(MSG_SWITCH_AP_SLAVER,0);	
			}
		}
	}
	else if (strcmp(app_manager_get_current_app(), APP_ID_USOUND) == 0)
	{
		if(remote_dev_info.bt_status>=1)
		{
			report_msg_to_main(MSG_SWITCH_AP_SLAVER,0);
		}
	}
}

void deal_sync_all_info_msg(struct uart_msg_info* msg_info)
{
	u8_t msg_type,msg_data=0;//,cur_ap;
	//int stream_type;
	memcpy(&remote_dev_info,msg_info,sizeof(struct uart_msg_info));
	#if 0
	if (strcmp(app_manager_get_current_app(), APP_ID_USOUND) == 0)
	{
		stream_type=AUDIO_STREAM_USOUND;
		cur_ap=0;
	}
	else if (strcmp(app_manager_get_current_app(), APP_ID_BTMUSIC) == 0)
	{
		
		stream_type=AUDIO_STREAM_MUSIC;
		cur_ap=1;
	}
	else if (strcmp(app_manager_get_current_app(), APP_ID_BTCALL) == 0)
	{
		stream_type=AUDIO_STREAM_VOICE;
		cur_ap=2;
	}
	else
	{
		stream_type=AUDIO_STREAM_LINEIN;
		cur_ap=3;
	}
	#endif
	SYS_LOG_INF("remote bt status:%d->usb status:%d->ap mode:%d->mute:%d\n",remote_dev_info.bt_status,remote_dev_info.usb_status,remote_dev_info.ap_mode,remote_dev_info.mute);
	//if(!systen_get_cascade_status()||(remote_dev_info.connented==0))
	{
		//SYS_LOG_INF("bt status:%d->usb status:%d\n",remote_dev_info.bt_status,remote_dev_info.usb_status);
		if (strcmp(app_manager_get_current_app(), APP_ID_BTMUSIC) == 0)
		{
			
			if(remote_dev_info.bt_status>=1)
			{
				report_msg_to_main(MSG_SWITCH_AP_SLAVER,0);	
				//cur_ap=3;
			}
			else if(remote_dev_info.usb_status==2)
			{
				if((bt_manager_get_status()&BT_STATUS_CONNECTED)!=BT_STATUS_CONNECTED)
				{
					report_msg_to_main(MSG_SWITCH_AP_SLAVER,0);	
					//cur_ap=3;
				}
			}
			else if(remote_dev_info.ap_mode==3)
			{
				system_sync_to_remote_start(ACK_OUT,CMD_SYNC_ALL);
			}
		}
		else if (strcmp(app_manager_get_current_app(), APP_ID_USOUND) == 0)
		{
			if(remote_dev_info.bt_status>=1)
			{
				report_msg_to_main(MSG_SWITCH_AP_SLAVER,0);
				///cur_ap=3;
			}
			else if(remote_dev_info.usb_status==2)
			{
				report_msg_to_main(MSG_SWITCH_AP_SLAVER,0);
				//cur_ap=3;
			}
			else if(remote_dev_info.ap_mode==3)
			{
				system_sync_to_remote_start(ACK_OUT,CMD_SYNC_ALL);
			}
		}
		else if (strcmp(app_manager_get_current_app(), APP_ID_BTCALL) == 0)
		{
			if(remote_dev_info.bt_status>=1)
			{
				report_msg_to_main(MSG_SWITCH_AP_SLAVER,0);	
				//cur_ap=3;
			}
			else if(remote_dev_info.usb_status==2)
			{
				report_msg_to_main(MSG_SWITCH_AP_SLAVER,0);	
			}
			else if(remote_dev_info.ap_mode==3)
			{
				system_sync_to_remote_start(ACK_OUT,CMD_SYNC_ALL);
			}
		}
		
	}
	#if 1
	if(strcmp(app_manager_get_current_app(), APP_ID_LINEIN) == 0)
	{
		if(remote_dev_info.ap_mode==1&&remote_dev_info.bt_status==0)
		{
			report_msg_to_main(MSG_SWITCH_AP_MASTER,0);	
			return;
		}
		if(remote_dev_info.mute!=system_get_mic_status())
		{		
			if(remote_dev_info.mute)
			{
				msg_type=MSG_MUTE_EN_EVENT;
			}
			else
			{
				msg_type=MSG_MUTE_DIS_EVENT;
			}
			report_msg_to_main(msg_type,msg_data);			
		}
		if(audio_aux_get_status())
		{
			audio_aux_sync_remote_volume(remote_dev_info.sync_vol);	
		}		
		if(remote_dev_info.bt_status==3)
		{
			audio_input_set_hung_led(2);
		}
		else if(remote_dev_info.bt_status==2)
		{
			audio_input_set_hung_led(1);
		}
		else
		{
			audio_input_set_hung_led(0);
		}
	}
	#endif
}

void report_uart_msg_to_main(u8_t msg_cmd,void* msg_str)
{
	struct app_msg  msg = {0};
	msg.type = msg_cmd;
	msg.ptr=msg_str;
	send_async_msg("main", &msg);
}

void deal_uart_msg_info(struct uart_data_format *p_reply)
{
	u8_t msg_type,msg_data=0,msg_cmd=0;
	SYS_LOG_INF("start deal msg!!!\n");
	deal_cascade_status_to_aux();
	#if 0
	if(p_reply->cmd==CMD_SYNC_CASCADE_STATUS||p_reply->cmd==CMD_SYNC_ALL)
	{
		k_sleep(2);
		system_sync_to_remote_start(ACK_NO,p_reply->cmd);
	}
	#else
	if(p_reply->cmd!=CMD_SYNC_POWEROFF)
	{
		system_sync_to_remote_start(ACK_NO,p_reply->cmd);			
	}
	#endif
	SYS_LOG_INF("cmd:%d\n",p_reply->cmd);
	switch(p_reply->cmd)
	{
		case CMD_SYNC_ALL:			
			deal_sync_all_info_msg(&p_reply->msg_info);
			if(sys_check_ap_ready())
			{
				systen_set_cascade_status(1);
			}
			else
			{	
				systen_set_cascade_status(0);
			}		
			switch_io_func_to_uart_rx();
			break;
		case CMD_SYNC_MUTE:
			if(p_reply->data[0])
			{
				msg_type=MSG_MUTE_EN_EVENT;
			}
			else
			{
				msg_type=MSG_MUTE_DIS_EVENT;
			}
			report_msg_to_main(msg_type,msg_data);
			break;
		case CMD_SYNC_VOLUME:
			msg_data=p_reply->data[0];
			msg_type=MSG_SYNC_VOL_EVENT;					
			report_msg_to_cur_ap(msg_type,msg_cmd,msg_data);
			break;
		case CMD_SYNC_KEY_ONOFF:
			msg_data=p_reply->data[0];
			msg_type=MSG_SYNC_KEY_MSG_EVENT;
			msg_cmd=CMD_KEY_ONOFF;
			report_msg_to_cur_ap(msg_type,msg_cmd,msg_data);
			break;
		case CMD_SYNC_KEY_HUNG:
			msg_data=p_reply->data[0];
			msg_type=MSG_SYNC_KEY_MSG_EVENT;	
			msg_cmd=CMD_KEY_HUNG;
			report_msg_to_cur_ap(msg_type,msg_cmd,msg_data);
			break;
		case CMD_SYNC_KEY_VOL_ADD:
			msg_data=p_reply->data[0];
			remote_dev_info.sync_vol=p_reply->data[0];
			msg_type=MSG_SYNC_KEY_MSG_EVENT;
			msg_cmd=CMD_KEY_VOL_ADD;
			report_msg_to_cur_ap(msg_type,msg_cmd,msg_data);
			break;
		case CMD_SYNC_KEY_VOL_SUB:
			msg_data=p_reply->data[0];
			remote_dev_info.sync_vol=p_reply->data[0];
			msg_type=MSG_SYNC_KEY_MSG_EVENT;	
			msg_cmd=CMD_KEY_VOL_SUB;
			report_msg_to_cur_ap(msg_type,msg_cmd,msg_data);
			break;
		case CMD_SYNC_MODE:
			msg_data=p_reply->data[0];
			break;
		case CMD_SYNC_BT_STATUS:
			remote_dev_info.bt_status=p_reply->data[0];
			remote_dev_info.ap_mode=p_reply->data[1];
			deal_remote_bt_status();
			break;
		
		case CMD_SYNC_USB_STATUS:
			remote_dev_info.usb_status=p_reply->data[0];
			remote_dev_info.usb_mute=p_reply->data[2];
			remote_dev_info.ap_mode=p_reply->data[1];
			deal_remote_usb_status();
			break;
		case CMD_SYNC_POWEROFF:
			memset(&remote_dev_info,0x0,sizeof(struct uart_msg_info));
			systen_set_cascade_status(0);
			deal_remote_poweroff();
			break;
		case CMD_SYNC_CHARGE_STATUS:
			if (strcmp(app_manager_get_current_app(), APP_ID_USOUND)==0)
			{
				usound_set_tts_tone(2);
			}
			else
			{
				sys_event_notify(SYS_EVENT_CHARGE_TTS);
			}
			
			break;
		case CMD_SYNC_LOWPOWER_STATUS:
			if (strcmp(app_manager_get_current_app(), APP_ID_LINEIN))
			{
				sys_event_notify(SYS_EVENT_BATTERY_LOW);
			}			
			break;
		case CMD_SYNC_CASCADE_STATUS:
			if((strcmp(app_manager_get_current_app(), APP_ID_LINEIN))&&get_sync_flag())
			{
				system_sync_to_remote_start(ACK_OUT,CMD_SYNC_ALL);
			}
			break;
		default:
			return;
	}
}
/**
 * uart1 rx recv dispatch
 *
 * @param
 *  p_data
 */
u8_t g_bat_status = 1;
u8_t g_mcu_reset = 0;
u8_t data_buf[32];
struct uart_data_format uart_msg;

void uart1_dispatch(     u8_t *p_data)
{
	struct uart_data_format *p_reply = (void *)p_data;
	u16_t writen_len = p_reply->data_len;
    //u8_t cmd = p_reply->cmd;

    //todo send event/msg base rx info
#if 0//def UART_DEBUG
    SYS_LOG_INF(" magic %x\n", p_reply->magic);

	//write output
    p_reply->magic = 0x3E;  //应答flag ">"

    SYS_LOG_INF(" reply %d,%x\n", writen_len, p_data[writen_len]);
    //追加/替换最后一个字符为"@"来做ack
    if(writen_len < UART_MTU)
    {
        p_data[writen_len] = 0x40;
        SYS_LOG_INF(" data %x,%x\n", p_data[writen_len-1], p_data[writen_len]);
        uart_pipe_send((u8_t *)p_reply, writen_len+1);
    }
    else
    {
        p_data[UART_MTU-1] = 0x40;
        uart_pipe_send((u8_t *)p_reply, UART_MTU);
    }
    print_buffer(p_data, 1, writen_len+1, 16, 0);
#else
	if(p_reply->magic!=MAGIC_HEAD)
	{
		if(p_reply->magic!=0xff)
		{
			SYS_LOG_INF(" magic head err:%x\n",p_reply->magic);
		}		
		return ;
	}
	if(p_reply->end!=MAGIC_END)
	{
		SYS_LOG_INF(" magic end err:%x\n",p_reply->end);
		return ;
	}
	if(p_reply->ack==ACK_NO)
	{
		if(p_reply->cmd!=CMD_SYNC_CASCADE_STATUS)
		{
			system_stop_sync();
		}		
		deal_cascade_status_to_aux();
		if(p_reply->cmd==CMD_SYNC_ALL)
		{
			memcpy(&remote_dev_info,&p_reply->msg_info,sizeof(struct uart_msg_info));
			if(!systen_get_cascade_status())
			{
				deal_ack_info_msg(&p_reply->msg_info);
			}
		}
		if(p_reply->cmd==CMD_SYNC_ALL&&remote_dev_info.ap_mode>=4)
		{
			systen_set_cascade_status(0);
		}
		else
		{
			systen_set_cascade_status(1);
		}				
		switch_io_func_to_uart_rx();
		return;
	}
	else if(p_reply->ack==ACK_OUT)
	{		
		if(writen_len!=0)
		{	
			#if 1
			SYS_LOG_INF("deal rx msg!!!\n");
			memcpy(&uart_msg,p_reply,sizeof(struct uart_data_format));
			report_uart_msg_to_main(MSG_UART_MSG,(void*)&uart_msg);
			#else
			u8_t msg_type,msg_data=0,msg_cmd=0;
		    SYS_LOG_INF("deal rx msg!!!\n");
			//if(p_reply->cmd==CMD_SYNC_ALL)
			deal_cascade_status_to_aux();
			if(p_reply->cmd!=CMD_SYNC_POWEROFF)
			{
				k_sleep(2);
				system_sync_to_remote_start(ACK_NO,p_reply->cmd);	
			}
			
			switch(p_reply->cmd)
			{
				case CMD_SYNC_ALL:
					
					deal_sync_all_info_msg(&p_reply->msg_info);
					systen_set_cascade_status(1);
					switch_io_func_to_uart_rx();
					break;
				case CMD_SYNC_MUTE:
					if(p_reply->data[0])
					{
						msg_type=MSG_MUTE_EN_EVENT;
					}
					else
					{
						msg_type=MSG_MUTE_DIS_EVENT;
					}
					report_msg_to_main(msg_type,msg_data);
					break;
				case CMD_SYNC_VOLUME:
					msg_data=p_reply->data[0];
					msg_type=MSG_SYNC_VOL_EVENT;					
					report_msg_to_cur_ap(msg_type,msg_cmd,msg_data);
					break;
				case CMD_SYNC_KEY_ONOFF:
					msg_data=p_reply->data[0];
					msg_type=MSG_SYNC_KEY_MSG_EVENT;
					msg_cmd=CMD_KEY_ONOFF;
					report_msg_to_cur_ap(msg_type,msg_cmd,msg_data);
					break;
				case CMD_SYNC_KEY_HUNG:
					msg_data=p_reply->data[0];
					msg_type=MSG_SYNC_KEY_MSG_EVENT;	
					msg_cmd=CMD_KEY_HUNG;
					report_msg_to_cur_ap(msg_type,msg_cmd,msg_data);
					break;
				case CMD_SYNC_KEY_VOL_ADD:
					msg_data=p_reply->data[0];
					msg_type=MSG_SYNC_KEY_MSG_EVENT;
					msg_cmd=CMD_KEY_VOL_ADD;
					report_msg_to_cur_ap(msg_type,msg_cmd,msg_data);
					break;
				case CMD_SYNC_KEY_VOL_SUB:
					msg_data=p_reply->data[0];
					msg_type=MSG_SYNC_KEY_MSG_EVENT;	
					msg_cmd=CMD_KEY_VOL_SUB;
					report_msg_to_cur_ap(msg_type,msg_cmd,msg_data);
					break;
				case CMD_SYNC_MODE:
					msg_data=p_reply->data[0];
					break;
				case CMD_SYNC_BT_STATUS:
					remote_dev_info.bt_status=p_reply->data[0];
					remote_dev_info.ap_mode=p_reply->data[1];
					deal_remote_bt_status();
					break;
				
				case CMD_SYNC_USB_STATUS:
					remote_dev_info.usb_status=p_reply->data[0];
					remote_dev_info.ap_mode=p_reply->data[1];
					deal_remote_usb_status();
					break;
				case CMD_SYNC_POWEROFF:
					memset(&remote_dev_info,0x0,sizeof(struct uart_msg_info));
					systen_set_cascade_status(0);
					deal_remote_poweroff();
					break;
				default:
					return;
			}
			#endif
			
			
		}
	}
   
#endif	
	return;
}
/**
 * exec in system workqueue
 */
static void uart1_cmd_handle(os_work *work)
{
	struct uart_buf_info *cmd_buf = NULL;
	#if 1
	u8_t i;
	for(i=0;i<UART_BUF_QUEUED;i++)
	{
		cmd_buf = k_fifo_get(&cmds_queue_uart1, K_NO_WAIT);

	    //SYS_LOG_INF(" %08x\n", (unsigned)cmd_buf);
		if (cmd_buf == NULL)
	    {
	        continue;
	    }
	    //SYS_LOG_INF(" %08x\n", (unsigned)cmd_buf->data);

		//dispatch handle
	    uart1_dispatch(cmd_buf->data);
		k_fifo_put(&avail_queue_uart1, cmd_buf);
	}
	#else
	cmd_buf = k_fifo_get(&cmds_queue_uart1, K_NO_WAIT);

    //SYS_LOG_INF(" %08x\n", (unsigned)cmd_buf);
	if (cmd_buf == NULL)
    {
        SYS_LOG_ERR("uart1: cmd_buf get error 3");
		return;
    }
    //SYS_LOG_INF(" %08x\n", (unsigned)cmd_buf->data);
	//dump
	//print_buffer(cmd_buf->data, 1, cmd_buf->data_info.data_len+1, 16, 0);
	//print_buffer(cmd_buf->data, 1, cmd_buf->data_info.data_len, 16, 0);

	//dispatch handle
    uart1_dispatch(cmd_buf->data);

	k_fifo_put(&avail_queue_uart1, cmd_buf);
	#endif
}

/**
 * notice this function exec in ISR context
 */
static u8_t *uart1_recv_cb(u8_t *buf, size_t *off)
{
    struct uart_data_format *cmds_buf = (void *) buf;
    struct uart_buf_info *new_buf;
    u16_t len;
	//printk("buf addr:0x%x\n",(unsigned)buf);
	
	//print_buffer(buf, 1, *off, 16, (u32_t)*buf);
    //SYS_LOG_INF("1> %08x, %ld,%ld\n", (unsigned)buf, *off, sizeof(*cmds_buf));
   
    if (cmds_buf->magic != MAGIC_HEAD) {
		if(cmds_buf->magic!=0xff)
		{
			SYS_LOG_ERR("uart1: RX magic error 0x%x,len:%ld", cmds_buf->magic,*off);
		}        
        //if(*off >= UART_MTU)
            *off = 0;
        return buf;
    }
#if 0
    if (*off < sizeof(*cmds_buf)) {
        SYS_LOG_ERR("uart1: RX data not enough 0");
        if(*off >= UART_MTU)
            *off = 0;
		return buf;
	}
#else
    //uart control的最小长度，防止拿到错误的数据长度
    if(*off < 0x03){
        //SYS_LOG_ERR("uart1: RX data not enough 0");
        if(*off >= UART_MTU)
            *off = 0;
        return buf;
    }
#endif
    //SYS_LOG_INF("2> %08x, %d,%ld\n", (unsigned)buf, cmds_buf->data_len, *off);

    len = cmds_buf->data_len;
	
    //防止buffer长度溢出，规避死循环
    if(len > UART_MTU){
        *off = 0;
        SYS_LOG_ERR("uart1: TX data_len err %d", len);
        return buf;
    }

    //判断输入长度是否达到格式要求，未达到则重新缓存
    if (*off < len) {
        //SYS_LOG_ERR("uart1: RX data not enough 1:%ld", *off);
        if(*off <= UART_MTU)    //防止超出buffer大小
        {
            return buf;
        }
        SYS_LOG_ERR("uart1: RX buf full");
    }
	printk("RX:\n");
	print_buffer(buf, 1, *off, 16, 0);
	#if 1
    new_buf =  k_fifo_get(&avail_queue_uart1, K_NO_WAIT);
    if (!new_buf) {
        SYS_LOG_ERR("uart1: RX overflow 2");
        *off = 0;
        return buf;
    }
	#endif
    k_fifo_put(&cmds_queue_uart1, CONTAINER_OF(buf, struct uart_buf_info, data));
    os_delayed_work_submit(&uart1_control_run_delaywork, UART_RXTX_INTERVAL);
	
    *off = 0;
	memset(new_buf->data, 0, UART_MTU);
    return new_buf->data;
}


/*initialize uart1*/
void uart1_setting_init(void)
{
	int i;
	struct uart_buf_info *buf;

	for (i = 0; i < UART_BUF_QUEUED; i++) {
		k_fifo_put(&avail_queue_uart1, &uart_buf[i]);
	}

	buf = k_fifo_get(&avail_queue_uart1, K_NO_WAIT);
	uart_pipe_register(buf->data, UART_MTU, uart1_recv_cb);

	SYS_LOG_INF("uart1 communication init\n");
	os_delayed_work_init(&uart1_control_run_delaywork, uart1_cmd_handle);
}

